/**
 * File: Semester.java
 * Author: Ben Stutsky
 * Team: Bob-omb Squad
 * Date: 4/18/11
 * Email: stutsky1@umbc.edu
 */
package clientApp;

import java.io.Serializable;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;

/**
 * The Class Semester.
 */
public class Semester implements Serializable {
	private static final long serialVersionUID = 8495589185058938453L;
	
	private boolean isOverridden = false;
	public static final int MAX_OVERRIDDEN = 22;
	public static final int MAX_UNOVERRIDDEN = 19;
	
	/** The season. */
	private int season;
	
	/** The year. */
	private int year;
	
	/** The is previous flag. */
	private boolean isPrevious;
	
	/** The course records. */
	private ArrayList<CourseRecord> courseRecords = new ArrayList<CourseRecord>();
	
	/* Written by Rotem- creates a semester for the current season
	   Just copied/ edited your code from generatePrevious() */
	public Semester() {
		DateFormat dateFormat = new SimpleDateFormat("yyyy MM");
		Date date = new Date();
		String theDate = dateFormat.format(date);
		String[] yearAndMonth = theDate.split(" ");
		
		season = getSeasonConst(yearAndMonth[1]);
		year = Integer.parseInt(yearAndMonth[0]);
		generatePrevious();
		isOverridden = false;
	}
	
	/**
	 * Constructor for cloning a semester.
	 *
	 * @param clone target semester for cloning
	 */
	public Semester(Semester clone)
	{
		season = clone.getSeason();
		year = clone.getYear();
		isPrevious = clone.isPrevious();
		courseRecords = clone.getCourseRecords();
		isOverridden = clone.isOverridden();
	}
	
	public Semester(int mySeason, int myYear)
	{
		season = mySeason;
		year = myYear;
		generatePrevious();
		isOverridden = false;
	}
	
	/**
	 * Instantiates a new semester.
	 *
	 * @param mySeason the my season
	 * @param myYear the my year
	 * @param previous the previous
	 */
	public Semester(int mySeason, int myYear, boolean overridden)
	{
		season = mySeason;
		year = myYear;
		generatePrevious();
		isOverridden = overridden;
	}
	
	/**
	 * Instantiates a new semester.
	 *
	 * @param mySeason the my season
	 * @param myYear the my year
	 * @param previous the previous
	 * @param courses the courses
	 */
	public Semester(int mySeason, int myYear, ArrayList<CourseRecord> courses)
	{
		season = mySeason;
		year = myYear;
		generatePrevious();
		isOverridden = false;
		// deep copy
		for(CourseRecord data : courses)
		{
			courseRecords.add(new CourseRecord(data));
		}
		
	}
	
	
	public Semester(int mySeason, int myYear, boolean overridden, ArrayList<CourseRecord> courses)
	{
		season = mySeason;
		year = myYear;
		generatePrevious();
		isOverridden = overridden;
		// deep copy
		for(CourseRecord data : courses)
		{
			courseRecords.add(new CourseRecord(data));
		}
		
	}
	
	public int getMaxCredits()
	{
		if(isOverridden)
		{
			return MAX_OVERRIDDEN;
		}
		return MAX_UNOVERRIDDEN;
	}
	
	public ArrayList<String> getCourseIDs()
	{
		ArrayList<String> myIDs = new ArrayList<String>();
		for(int i = 0; i != courseRecords.size(); i++)
		{
			myIDs.add(courseRecords.get(i).getCourseID());
		}
		return myIDs;
	}
	
	public void setOverriden(boolean override)
	{
		isOverridden = override;
	}
	
	public boolean isOverridden()
	{
		return isOverridden;
	}
	
	private void generatePrevious()
	{
		DateFormat dateFormat = new SimpleDateFormat("yyyy MM");
		Date date = new Date();
		String theDate = dateFormat.format(date);
		String[] yearAndMonth = theDate.split(" ");
		int presSeason = getSeasonConst(yearAndMonth[1]);
		int presYear = Integer.parseInt(yearAndMonth[0]);
		
		if(presYear > year)
		{
			isPrevious = true;
		}
		else if(presYear < year)
		{
			isPrevious = false;
		}
		else
		{
			if(presSeason == season)
			{
				isPrevious = false;
			}
			else if(presSeason > season)
			{
				isPrevious = false;
			}
			else
			{
				isPrevious = true;
			}
		}
	}
	
	/**
	 * Gets the season.
	 *
	 * @return the season
	 */
	public int getSeason() 
	{
		return season;
	}

	/**
	 * Sets the season.
	 *
	 * @param mySeason the new season
	 */
	public void setSeason(int mySeason) 
	{
		this.season = mySeason;
	}

	/**
	 * Gets the year.
	 *
	 * @return the year
	 */
	public int getYear() 
	{
		return year;
	}

	/**
	 * Sets the year.
	 *
	 * @param myYear the new year
	 */
	public void setYear(int myYear) 
	{
		this.year = myYear;
	}

	/**
	 * Checks if this is a previous semester.
	 *
	 * @return true, if it is previous
	 */
	public boolean isPrevious() 
	{
		return isPrevious;
	}

	/**
	 * Sets the previous flag.
	 *
	 * @param previous the new previous flag
	 */
	public void calcPrevious() 
	{
		generatePrevious();
	}

	/**
	 * Returns deep copy of course record given course code
	 * 
	 * @param courseCode the code for the courseRecord to retrieve
	 */
	public CourseRecord getCourseRecord(String courseCode)
	{
		for(int i = 0; i != courseRecords.size(); i++)
		{
			if(courseRecords.get(i).getCourseID().compareTo(courseCode) == 0)
			{
				return new CourseRecord(courseRecords.get(i));
			}	
		}	
		return null;
	}
	
	/**
	 * Gets the course records.
	 *
	 * @return the course records as a deep copy
	 */
	public ArrayList<CourseRecord> getCourseRecords() 
	{
		ArrayList<CourseRecord> data = new ArrayList<CourseRecord>();
		for(CourseRecord temp : courseRecords)
		{
			data.add(new CourseRecord(temp));
		}
		return data;
	}
	
	/**
	 * Sets the course records, usually if there are none taken yet. This will overwrite previously entered course records.
	 *
	 * @param myCourseRecords the new course records
	 */
	/*
	private void setCourseRecords(ArrayList<CourseRecord> myCourseRecords) 
	{
		ArrayList<CourseRecord> data = new ArrayList<CourseRecord>();
		for(CourseRecord temp : myCourseRecords)
		{
			data.add(new CourseRecord(temp));
		}
		courseRecords = data;
	}
	 */
	
	/**
	 * Removes the course record from the semester.
	 *
	 * @param courseCode the course code
	 * @return true, if successful
	 */
	public boolean removeCourseRecord(String courseCode)
	{
		for(int i = 0; i != courseRecords.size(); i++)
		{
			if(courseRecords.get(i).getCourseID().compareTo(courseCode) == 0)
			{
				courseRecords.remove(i);
				return true;
			}	
		}	
		return false;
	}
	
	public boolean setCourseRecordGrade(String courseID, char grade)
	{
		CourseRecord temp = getCourseRecordWithID(courseID);
		if(temp != null)
		{
			temp.setGrade(grade);
			return true;
		}
		return false;
	}
	
	public boolean setCourseRecordNotes(String courseID, String notes)
	{
		CourseRecord temp = getCourseRecordWithID(courseID);
		if(temp != null)
		{
			temp.setNotes(notes);
			return true;
		}
		return false;
	}
	
	private CourseRecord getCourseRecordWithID(String courseID)
	{
		for(int i = 0; i != courseRecords.size(); i++)
		{
			CourseRecord temp = courseRecords.get(i);
			if(temp.getCourseID().compareTo(courseID) == 0)
			{
				return temp;
			}
		}
		return null;
	}
	
	private int getSeasonConst(String month)
	{
		int myMonth = Integer.parseInt(month);
		
		switch (myMonth)
		{
			case 1:
				return ProjectConstants.WINTER;
			case 2:
				return ProjectConstants.SPRING;
			case 3:
				return ProjectConstants.SPRING;
			case 4:
				return ProjectConstants.SPRING;
			case 5:
				return ProjectConstants.SPRING;
			case 6:
				return ProjectConstants.SUMMER;
			case 7:
				return ProjectConstants.SUMMER;
			case 8:
				return ProjectConstants.SUMMER;
			case 9:
				return ProjectConstants.FALL;
			case 10:
				return ProjectConstants.FALL;
			case 11:
				return ProjectConstants.FALL;
			case 12:
				return ProjectConstants.FALL;
			default:
				return 0;
		}
	}
	
	/**
	 * Adds the course record to the semester.
	 *
	 * @param newCourseRecord the new course record
	 */
	public void addCourseRecord(CourseRecord newCourseRecord)
	{
		courseRecords.add(new CourseRecord(newCourseRecord));
	}

	public String toString()
	{
		String retString = "";
		
		retString += "Season: " + ProjectConstants.getSeasonString(getSeason()) + "\n";
		retString += "Year: " + getYear() + "\n";
		retString += "Previous: " + isPrevious() + "\n";
		
		for(CourseRecord myCR : courseRecords)
		{
			retString += myCR.toString() + "\n";
		}
		
		return retString;
	}
	
	public static void main(String[] args)
	{
		Semester mySem1 = new Semester(ProjectConstants.FALL, 2009);
		Semester mySem2 = new Semester(ProjectConstants.SPRING, 2010);
		Semester mySem3 = new Semester(ProjectConstants.FALL, 2010);
		Semester mySem4 = new Semester(ProjectConstants.SPRING, 2011);
		
		CourseRecord myCR11 = new CourseRecord("CMSC201", 'A', "This is my 201. Rofl.");
		CourseRecord myCR12 = new CourseRecord("MATH151", 'B', "This is my 201. Rofl.");
		CourseRecord myCR13 = new CourseRecord("HEBR101", 'A', "This is my 201. Rofl.");
		CourseRecord myCR14 = new CourseRecord("ENG100", 'A', "This is my 201. Rofl.");
		
		CourseRecord myCR21 = new CourseRecord("MATH221", 'A', "This is my 201. Rofl.");
		CourseRecord myCR24 = new CourseRecord("CMSC304", 'B', "This is my 201. Rofl.");
		CourseRecord myCR22 = new CourseRecord("CMSC202", 'A', "This is my 202. Rofl.");
		CourseRecord myCR23 = new CourseRecord("CMSC203", 'A', "This is my 203. Rofl.");
		CourseRecord myCR25 = new CourseRecord("HEBR102", 'A', "This is my 201. Rofl.");
		
		CourseRecord myCR31 = new CourseRecord("CMSC313", 'A', "This is my 201. Rofl.");
		CourseRecord myCR32 = new CourseRecord("HEBR201", 'B', "This is my 201. Rofl.");
		CourseRecord myCR33 = new CourseRecord("CHEM101", 'B', "This is my 201. Rofl.");
		CourseRecord myCR34 = new CourseRecord("CMSC341", 'B', "This is my 341. Rofl.");
		
		CourseRecord myCR41 = new CourseRecord("CMSC345", ProjectConstants.NO_GRADE, "This is my 201. Rofl.");
		CourseRecord myCR42 = new CourseRecord("CMSC331", ProjectConstants.NO_GRADE, "This is my 201. Rofl.");
		CourseRecord myCR43 = new CourseRecord("CHEM102", ProjectConstants.NO_GRADE, "This is my 201. Rofl.");
		CourseRecord myCR44 = new CourseRecord("STAT355", ProjectConstants.NO_GRADE, "This is my 201. Rofl.");
		
		mySem1.addCourseRecord(myCR11);
		mySem1.addCourseRecord(myCR12);
		mySem1.addCourseRecord(myCR13);
		mySem1.addCourseRecord(myCR14);
		
		mySem2.addCourseRecord(myCR21);
		mySem2.addCourseRecord(myCR22);
		mySem2.addCourseRecord(myCR23);
		mySem2.addCourseRecord(myCR24);
		mySem2.addCourseRecord(myCR25);
		
		mySem3.addCourseRecord(myCR31);
		mySem3.addCourseRecord(myCR32);
		mySem3.addCourseRecord(myCR33);
		mySem3.addCourseRecord(myCR34);
		
		mySem4.addCourseRecord(myCR41);
		mySem4.addCourseRecord(myCR42);
		mySem4.addCourseRecord(myCR43);
		mySem4.addCourseRecord(myCR44);
		
		System.out.println("Printing Semesters: ");
		System.out.println(mySem1);
		System.out.println(mySem2);
		System.out.println(mySem3);
		System.out.println(mySem4);
		
		System.out.println("\ntest get course IDS\n");
		for(String ID: mySem1.getCourseIDs() )
		{
			System.out.println(ID);
		}
		
		System.out.println("\ntest remove course record\n");
		mySem1.removeCourseRecord("ENG100");
		for(String ID: mySem1.getCourseIDs() )
		{
			System.out.println(ID);
		}
		
		System.out.println("\ntest set course record grade\n");
		mySem4.setCourseRecordGrade("CMSC345", 'A');
		for(CourseRecord cr: mySem4.getCourseRecords() )
		{
			System.out.println(cr);
		}
		
		System.out.println("\ntest set course record note\n");
		mySem4.setCourseRecordNotes("CMSC345", "THIS IS MY NOTE ROFL NOOB");
		for(CourseRecord cr: mySem4.getCourseRecords() )
		{
			System.out.println(cr);
		}
		
		System.out.println("\ntest get max creds\n");
		System.out.println("Max Creds: " + mySem4.getMaxCredits());
		System.out.println("Is override: " + mySem4.isOverridden() + "\n");
		
		System.out.println("\ntest set override\n");
		mySem4.setOverriden(true);
		System.out.println("Max Creds: " + mySem4.getMaxCredits());
		System.out.println("Is override: " + mySem4.isOverridden() + "\n");
		
		System.out.println("\ntest add course\n");
		mySem4.addCourseRecord(new CourseRecord("ENG100", 'A', "This is my 201. Rofl."));
		for(CourseRecord cr: mySem4.getCourseRecords() )
		{
			System.out.println(cr);
		}
	}
}
